const { menu } = require('../models/menu');
const Joi = require('joi');
const validationMiddleware = require('../middleware/validate');
const response = require("../utils/response");
const router = require('koa-router')();
const { handleDatabaseError, dealNotEmpty } = require("../utils/dberrordeal");
const { verify } = require("../utils/auth");
const rulesSchema = {
    '/addmenu': Joi.object({
        name: dealNotEmpty('路由名称'),
    }),
    '/putmenu': Joi.object({
        name: dealNotEmpty('路由名称'),
        id: dealNotEmpty('路由id'),
    }),
    '/getmenud': Joi.object({
        id: dealNotEmpty('路由id'),
    }),
    '/addbtnrole': Joi.object({
        menuId: dealNotEmpty('菜单id'),
        color: dealNotEmpty('按钮颜色'),
        name: dealNotEmpty('按钮名称'),
        code: dealNotEmpty('按钮标识'),
    }),
    '/getbtnrole': Joi.object({
        id: dealNotEmpty('菜单id'),
    }),
    '/putbtnrole': Joi.object({
        data: Joi.object({
            menuId: dealNotEmpty('菜单id'),
            color: dealNotEmpty('按钮颜色'),
            name: dealNotEmpty('按钮名称'),
            code: dealNotEmpty('按钮标识'),
        }),
        did: dealNotEmpty('按钮id'),
    }),
    '/deletebtnrole': Joi.object({
        id: dealNotEmpty('菜单id'),
        did: dealNotEmpty('按钮id'),
    }),
    '/delmenu': Joi.object({
        id: dealNotEmpty('路由id'),
    }),
}


router.post('/addbtnrole', validationMiddleware(rulesSchema), async (ctx, next) => {
    let data = ctx.request.body;
    let res = await menu.findOneAndUpdate({ _id: data.menuId }, {
        $push: {
            btnRoles: data
        }
    });
    if (res) {
        response.success(ctx, {});
    } else {
        response.error(ctx, {});
    }
});

router.post('/getbtnrole', async (ctx, next) => {
    let data = ctx.request.body;

    let res = await menu.findOne({ _id: data.id }).select('btnRoles -_id');

    if (res) {
        response.success(ctx, { data: res });
    } else {
        response.error(ctx, {});
    }
});

router.post('/putbtnrole', async (ctx, next) => {
    let data = ctx.request.body;

    let res = await menu.updateOne(
        { _id: data.data.menuId },
        { $set: { "btnRoles.$[element]": data.data } },
        { arrayFilters: [{ "element._id": data.did }] });

    if (res) {
        response.success(ctx, {});
    } else {
        response.error(ctx, {});
    }
});

router.post('/deletebtnrole', async (ctx, next) => {
    let data = ctx.request.body;
    let res = await menu.findOneAndUpdate({ _id: data.id }, { $pull: { btnRoles: { _id: data.did } } });
    if (res) {
        response.success(ctx, {});
    } else {
        response.error(ctx, {});
    }
});

router.post('/addmenu', validationMiddleware(rulesSchema), async (ctx, next) => {
    let data = ctx.request.body;
    let parentId = data.pid || 0;
    data.parentId = parentId;
    data.isMenu = data.ism;
    await menu.create(data).then(res => {
        response.success(ctx, {});
    }).catch(err => {
        handleDatabaseError(ctx, err, '路由名称重复');
    }
    );
});

router.post('/putmenu', validationMiddleware(rulesSchema), async (ctx, next) => {
    let data = ctx.request.body;

    let parentId = data.pid || 0;
    data.parentId = parentId;
    data.isMenu = data.ism;

    let res = await menu.findOneAndUpdate({ _id: data.id }, { $set: data }, { returnDocument: 'after' });
    if (res) {
        response.success(ctx, {});
    } else {
        response.error(ctx, {});
    }
});

router.post('/getmenud', validationMiddleware(rulesSchema), async (ctx, next) => {
    let data = ctx.request.body;
    let res = await menu.findOne({ _id: data.id });
    if (res) {
        response.success(ctx, { data: res });
    } else {
        response.error(ctx, {});
    }
});

const buildTree = (data) => {
    // 创建一个映射表来存储所有节点，以便快速查找
    const map = new Map();
    data.forEach(item => {
        map.set(item._id.toString(), { ...item._doc, _id: item._id.toString(), children: [] });
    });

    // 创建根节点数组
    var tree = [];
    data.forEach(item => {
        if (item.parentId === '0') {
            // 如果是根节点，则直接添加到树中
            tree.push(map.get(item._id.toString()));
            tree.sort((a, b) => a.order - b.order);
        } else {
            // 否则找到其父节点并添加为子节点
            const parent = map.get(item.parentId);
            if (parent) {
                parent.children.push(map.get(item._id.toString()));
                parent.children.sort((a, b) => a.order - b.order);
            }
        }
    });

    // 递归函数：为每个节点添加 ancestors 属性
    const addAncestors = (node, ancestors = []) => {
        if (ancestors.length !== 0) {
            node.ancestors = [...ancestors, node.name];
        }

        for (const child of node.children) {
            addAncestors(child, [...ancestors, node.name]);
        }
    }

    // 对每个根节点调用 addAncestors
    tree.forEach(root => addAncestors(root));
    return tree;
}

router.get('/getmenulist',verify, async (ctx, next) => {
    let res = await menu.find();
    if (res) {
        response.success(ctx, { data: buildTree(res) });
    } else {
        response.error(ctx, {});
    }
});

router.post('/delmenu', async (ctx, next) => {
    let data = ctx.request.body;

    let item=await menu.find({parentId:data.id});

    if(item.length!==0){
        for(let e of item){
            await menu.findOneAndDelete({_id:e._id});
        }
    }

    let res = await menu.findOneAndDelete({ _id: data.id });
    if (res) {
        response.success(ctx, {});
    } else {
        response.error(ctx, {});
    }
});

module.exports = router;
